﻿Imports Microsoft.VisualBasic

Namespace WebApi
    Namespace Linkedin
        Public Class LinkedinClient

            Private webClient As WebApi.Net.WebClient

            Public Sub New(oauth2 As WebApi.Oauth.Oauth2)

                Me.webClient = New WebApi.Net.WebClient
                Me.webClient.oAuth2 = oauth2

            End Sub

            Public Property LastError As Net.ServiceError
            Private Function Download(address As String) As String

                Dim Res = Encoding.UTF8.GetString(Me.webClient.DownloadData(address))

                webClient.postParams.Clear()

                If Me.webClient.StatusCode <> 200 Then

                    Me.LastError = New Net.ServiceError With {
                        .webClient = Me.webClient,
                       .ResError = Res,
                       .Net = WebApi.Type.LINKEDIN
                   }

                    Select Case Me.webClient.StatusCode
                        Case 500, 502, 503, 504
                            'Internal Server Error
                            'Bad Gateway
                            'Service Unavailable
                            'Gateway timeout

                            'Me.LastError = New Net.ServiceError With {.Message = Me.webClient.StatusCodeDescr, .Code = Me.webClient.StatusCode}
                            Me.LastError.Code = Me.webClient.StatusCode
                            Me.LastError.Message = Me.webClient.StatusCodeDescr

                            Net.ExceptionBase.ThrowException(New Net.ExceptionConnectionServer With {.ServiceError = Me.LastError})

                        Case Else

                            Try
                                'Dim Err As ServiceErrors
                                'Err = MyApp.JSONDeserialize(Of ServiceErrors)(Res)

                                'Me.LastError.Code = Err.error.code
                                'Me.LastError.Message = Err.error.message

                            Catch ex As Exception

                                Me.LastError.Code = Me.webClient.StatusCode
                                Me.LastError.Message = Res

                            End Try


                            Select Case Me.webClient.StatusCode

                                Case 400
                                    'Unauthorized
                                    Select Case Me.LastError.Code
                                        Case 190
                                            '190 not authorized application
                                            Net.ExceptionBase.ThrowException(New Net.ExceptionAPIAccount With {.ServiceError = Me.LastError})

                                    End Select

                            End Select




                    End Select

                    Net.ExceptionBase.ThrowException(New Net.ExceptionBase With {.ServiceError = Me.LastError})

                End If

                Return Res

            End Function

#Region "GENERIC ACCOUNT FUNCTIONS"

            Public Function GetAccountsLookup(Of tres)(ids As String, type As String, fields As List(Of String), AddQueryString As String) As Results(Of tres)

                Dim f As String = ""
                If fields IsNot Nothing AndAlso fields.Count > 0 Then
                    f = ":(" & String.Join(",", fields) & ")"
                End If

                Dim i As String = ""
                If ids <> "" Then
                    i = "::(" & ids & ")"
                End If

                Dim Uri As New UriBuilder(SF("https://api.linkedin.com/v1/{0}{1}{2}", type, i, f))

                Dim queryString = HttpUtility.ParseQueryString(AddQueryString)

                queryString.Add("format", "json")

                Uri.Query = queryString.ToString

                Dim Res = Me.Download(Uri.Uri.AbsoluteUri)
                'Return Res
                Return MyApp.JSONDeserializeObj(Of Results(Of tres))(Res)


            End Function

            Public Function GetUpdates(Of tres)(id As String, type As String, fields As List(Of String)) As Results(Of tres)

                Dim f As String = ""
                If fields IsNot Nothing AndAlso fields.Count > 0 Then
                    f = ":(" & String.Join(",", fields) & ")"
                End If


                Dim Uri As New UriBuilder(SF("https://api.linkedin.com/v1/{0}/{1}/updates{2}", type, id, f))

                Dim queryString = HttpUtility.ParseQueryString("") 'AddQueryString

                queryString.Add("format", "json")

                queryString.Add("event-type", "status-update")
                queryString.Add("count", "200")

                Uri.Query = queryString.ToString

                Dim Res = Me.Download(Uri.Uri.AbsoluteUri)
                'Return Res
                Return MyApp.JSONDeserializeObj(Of Results(Of tres))(Res)


            End Function

            Public Function PostShares(id As String, type As String) As String

                id = 2710232
                type = "companies"

                Dim Uri As New UriBuilder(SF("https://api.linkedin.com/v1/{0}/{1}/shares", type, id))

                Dim queryString = HttpUtility.ParseQueryString("") 'AddQueryString

                queryString.Add("format", "json")

                Dim m = New With {.visibility = New With {.code = "anyone"}, .comment = "lollo prova"}

                webClient.postParams.Add("*", MyApp.JSONSerialize(m))


                queryString.Add("event-type", "status-update")
                queryString.Add("count", "200")

                Uri.Query = queryString.ToString

                Dim Res = Me.Download(Uri.Uri.AbsoluteUri)
                Return Res
                'Return MyApp.JSONDeserializeObj(Of Results(Of tres))(Res)


            End Function

            Public Function GetUpdateComm(Of tres)(id As String, updateid As String, type As String, typeComm As String) As Results(Of tres)

                'update-comments likes
                Dim Uri As New UriBuilder(SF("https://api.linkedin.com/v1/{0}/{1}/updates/key={2}/{3}", type, id, updateid, typeComm))

                Dim queryString = HttpUtility.ParseQueryString("")

                queryString.Add("format", "json")

                queryString.Add("count", "100")

                Uri.Query = queryString.ToString

                Dim Res = Me.Download(Uri.Uri.AbsoluteUri)
                'Return Res
                Return MyApp.JSONDeserializeObj(Of Results(Of tres))(Res)


            End Function
            Public Function GetConnections(Of tres)(id As String, type As String) As Results(Of tres)

                'update-comments likes
                Dim Uri As New UriBuilder(SF("https://api.linkedin.com/v1/{0}/{1}/connections", type, id))

                Dim queryString = HttpUtility.ParseQueryString("")

                queryString.Add("format", "json")

                'queryString.Add("count", "100")

                Uri.Query = queryString.ToString

                Dim Res = Me.Download(Uri.Uri.AbsoluteUri)
                'Return Res
                Return MyApp.JSONDeserializeObj(Of Results(Of tres))(Res)


            End Function

#End Region



#Region "USER FUNCTIONS"

            Public Function GetCurrUser() As People

                Return Me.GetUsersLookup("~").values(0)
                'Return GetAccountsLookup(Of People)("~", "people", Nothing, "").values(0)

            End Function

            Public Function GetUsersLookup(ids As String) As Results(Of People)

                Return GetAccountsLookup(Of People)(ids, "people", People.DefFields, "")

            End Function

            Public Function GetCurrUserConnections() As Results(Of People)

                Return Me.GetUserConnections("~")

            End Function
            Public Function GetUserConnections(user As String) As Results(Of People)

                Return Me.GetConnections(Of People)(user, "people")

            End Function


#End Region
            '

#Region "COMPANIES FUNCTIONS"

            Public Function GetCompanyPosts(id As String) As Results(Of Update(Of companyStatusUpdate))

                Return Me.GetUpdates(Of Update(Of companyStatusUpdate))(id, "companies", companyStatusUpdate.DefFields)


            End Function
            Public Function GetCompanyPostComments(id As String, updateid As String) As Results(Of Comment)

                Return Me.GetUpdateComm(Of Comment)(id, updateid, "companies", "update-comments")


            End Function
            Public Function GetCompanyPostLikes(id As String, updateid As String) As Results(Of [Like])

                Return Me.GetUpdateComm(Of [Like])(id, updateid, "companies", "likes")


            End Function

            Public Function GetCompaniesLookup(ids As String) As Results(Of Company)

                Return GetAccountsLookup(Of Company)(ids, "companies", Company.DefFields, "")

            End Function
            Public Function GetCompaniesAdmin() As Results(Of Company)

                Return GetAccountsLookup(Of Company)("", "companies", Company.DefFields, "is-company-admin=true")

            End Function

#End Region



            'Public Function GetCompaniesLookup(ids As String, fields As List(Of String)) As People

            '    Dim f As String = ""
            '    If fields IsNot Nothing AndAlso fields.Count > 0 Then
            '        f = ":(" & String.Join(",", fields) & ")"
            '    End If

            '    Dim Uri As New UriBuilder(SF("https://api.linkedin.com/v1/companies::({0}){1}", ids, f))

            '    Dim queryString = HttpUtility.ParseQueryString("")

            '    queryString.Add("format", "json")

            '    Uri.Query = queryString.ToString

            '    Dim Res = Me.Download(Uri.Uri.AbsoluteUri)
            '    'Return Res
            '    Return MyApp.JSONDeserialize(Of People)(Res)


            'End Function



        End Class

        Public Class Results(Of tres)

            Public Property values As New List(Of tres)
            Public Property _total As Integer

        End Class
        Public Class People

            Public Property id As String
            Public Property firstname As String
            Public Property lastname As String
            Public Property formattedname As String
            Public Property headline As String

            'Public Property connections As Integer

            Public Property pictureurl As String
            Public Property publicprofileurl As String

            Public Property location As Location

            Public Property numconnections As Integer


            Public Shared Function DefFields() As List(Of String)

                Return New List(Of String) From {
                    "id", "first-name", "last-name", "formatted-name",
                    "picture-url", "public-profile-url", "location", "headline",
                    "num-connections"
                }


                ', "positions"
            End Function

            'Public Shared Function DefFieldsLookup() As List(Of String)

            '    Return New List(Of String) From {
            '        "name", "link", "username", "location",
            '        "picture", "accounts"
            '    }

            'End Function

            'accounts

        End Class
        Public Class Company

            Public Property id As String
            Public Property name As String
            Public Property universalname As String
            Public Property description As String

            Public Property websiteurl As String
            Public Property squarelogourl As String

            Public Property numfollowers As Integer


            Public Shared Function DefFields() As List(Of String)

                Return New List(Of String) From {
                    "id", "name", "universal-name", "description", "locations",
                    "website-url", "square-logo-url", "num-followers"
                }


                ', "positions"
            End Function

        End Class
        Public Class Update(Of tres)

            Public Property updateKey As String
            Public Property updateType As String
            Private _timestamp As Date
            Public Property timestamp() As Object
                Get
                    Return _timestamp
                End Get
                Set(ByVal value As Object)
                    _timestamp = Utils.Conv.ToTimeStampDate(value)
                End Set
            End Property


            Public Property updateContent As UpdateContent(Of tres)

            Public Property updatecomments As Results(Of Comment)
            Public Property likes As Results(Of [Like])



        End Class

        Public Class UpdateContent(Of tres)

            Public Property company As Company
            Public Property companystatusupdate As tres

        End Class
        Public Class companyStatusUpdate

            Public Property share As UpdateShare

            Public Shared Function DefFields() As List(Of String)

                Return New List(Of String) From {
                    "updateKey", "updateType", "timestamp", "updateContent",
                    "update-comments", "likes"
                }


                ', "positions"
            End Function
        End Class

        Public Class UpdateShare

            Public Property id As String
            Public Property author As People
            Public Property comment As String

        End Class

        Public Class [Like]

            Public Property company As Company
            Public Property person As People
            Private _timestamp As Date
            Public Property timestamp() As Object
                Get
                    Return _timestamp
                End Get
                Set(ByVal value As Object)
                    _timestamp = Utils.Conv.ToTimeStampDate(value)
                End Set
            End Property

        End Class
        Public Class Comment

            Public Property id As String
            Public Property comment As String
            Public Property company As Company
            Public Property person As People
            Private _timestamp As Date
            Public Property timestamp() As Object
                Get
                    Return _timestamp
                End Get
                Set(ByVal value As Object)
                    _timestamp = Utils.Conv.ToTimeStampDate(value)
                End Set
            End Property

        End Class


        Public Class Location

            Public Property country As country
            Public Property name As String

        End Class
        Public Class country
            Public Property code As String
        End Class

    End Namespace
End Namespace
